package user.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import core.constants.Constant;
import core.domain.ListDataInfo;
import core.enums.ExamListType;
import core.enums.ResultCode;
import core.exception.ServiceException;
import core.threadLocal.ThreadLocalUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import user.domain.exam.Exam;
import user.domain.exam.dto.ExamQueryDTO;
import user.domain.exam.vo.ExamVO;
import user.domain.user.UserExam;
import user.manager.ExamCacheManage;
import user.mapper.CExamMapper;
import user.mapper.CUserExamMapper;
import user.service.IUserExamService;

import java.time.LocalDateTime;
import java.util.List;

@Service
public class UserExamServiceImpl implements IUserExamService {

    @Autowired
    private CUserExamMapper userExamMapper;

    @Autowired
    private CExamMapper examMapper;

    @Autowired
    private ExamCacheManage examCacheManage;

    @Override
    public int enter(String token, Long examId) {
        Exam exam = examMapper.selectById(examId);
        if(exam == null) {
            throw new ServiceException(ResultCode.EXAM_NOT_EXISTS);
        }
        if(exam.getStartTime().isBefore(LocalDateTime.now())){
            throw new ServiceException(ResultCode.EXAM_STARTED);
        }
//        Long userId = Long.parseLong(JWTUtils.getUserId(token, secret));
        Long userId = ThreadLocalUtils.get(Constant.USER_ID, Long.class);
        UserExam userExam = userExamMapper.selectOne(new LambdaQueryWrapper<UserExam>()
                .eq(UserExam::getUserId, userId)
                .eq(UserExam::getExamId, examId));
        if(userExam != null) {
            throw new ServiceException(ResultCode.USER_REP_APPLY);
        }
        userExam = new UserExam();
        userExam.setUserId(userId);
        userExam.setExamId(examId);
        examCacheManage.addUserExamList(userId, examId);
        return userExamMapper.insert(userExam);
    }

    @Override
    public ListDataInfo redisMyList(ExamQueryDTO query) {
        // 从 redis 中获取数据
        query.setType(ExamListType.USER_EXAM_LIST.getValue());
        Long userId = ThreadLocalUtils.get(Constant.USER_ID, Long.class);
        Long listSize = examCacheManage.getListSize(query.getType(), userId);
        List<ExamVO> list;
        if (listSize == null || listSize == 0) {  // 如果 redis 中没有数据
            PageHelper.startPage(query.getPageNum(), query.getPageSize());
            list = userExamMapper.selectUserExamList(userId);   // 从数据库中获取数据
            examCacheManage.refreshCache(query.getType(), userId); // 刷新 redis 缓存
            listSize = new PageInfo<>(list).getTotal();
        } else {  // 如果 redis 中有数据

            list = examCacheManage.getExamVOList(query, userId); // 从 redis 中获取数据
            listSize = examCacheManage.getListSize(query.getType(), userId);
        }
        return ListDataInfo.success(list, listSize.intValue());
    }
}
